
    <!DOCTYPE html>
    <html lang="zh-CN">
    <head>
      <meta charset="UTF-8">
      <meta name="viewport" content="width=device-width, initial-scale=1.0">
      <title>优化高并发场景下的数据库查询性能 - 学习卡片</title>
      <style>
        body { font-family: sans-serif; background-color: #f0f8ff; color: #333; display: flex; flex-direction: column; align-items: center; padding: 50px 20px; }
        .header h1 { font-size: 32px; }
        .grid-container { display: grid; grid-template-columns: repeat(3, 1fr); gap: 28px; width: 100%; max-width: 1200px; }
        .card-container { perspective: 1200px; cursor: pointer; height: 250px; }
        .card { width: 100%; height: 100%; position: relative; transform-style: preserve-3d; transition: transform 0.7s; border-radius: 16px; box-shadow: 0 4px 16px rgba(0,0,0,0.08); }
        .card-container.flipped .card { transform: rotateY(180deg); }
        .card-face { position: absolute; width: 100%; height: 100%; backface-visibility: hidden; display: flex; flex-direction: column; box-sizing: border-box; border-radius: 16px; background-color: #fff; padding: 24px; }
        .card-back { background-color: #f0fff4; transform: rotateY(180deg); justify-content: space-between; }
        .card-category { font-size: 14px; color: #0052d9; margin-bottom: 8px; font-weight: 500; }
        .card-question { font-size: 20px; font-weight: 500; flex-grow: 1; display: flex; align-items: center; justify-content: center; text-align: center; }
        .card-answer-wrapper { flex-grow: 1; overflow-y: auto; }
        .card-answer { font-size: 15px; line-height: 1.7; }
        .card-footer { font-size: 13px; color: #8a919f; border-top: 1px solid #f0f0f0; padding-top: 16px; margin-top: 16px; }
        .card-source { font-size: 13px; color: #8a919f; border-top: 1px solid #f0f0f0; padding-top: 12px; margin-top: 12px; }
      </style>
    </head>
    <body>
      <div class="header">
        <h1>优化高并发场景下的数据库查询性能 - 学习卡片</h1>
      </div>
      <div class="grid-container">
        
    <div class="card-container" onclick="this.classList.toggle('flipped');">
      <div class="card">
        <div class="card-face card-front">
          <div class="card-category">理论</div>
          <div class="card-question">在高并发场景下，分析数据库性能瓶颈时，常见的瓶颈来源有哪些？</div>
          <div class="card-footer">点击卡片查看答案</div>
        </div>
        <div class="card-face card-back">
          <div class="card-category">理论</div>
          <div class="card-answer-wrapper">
            <div class="card-answer">常见的性能瓶颈有五类：CPU瓶颈（计算密集型任务）、内存瓶颈（缓存或连接池导致内存占用高）、I/O瓶颈（磁盘或网络读写慢）、锁竞争（高并发下锁争用导致线程等待）以及查询效率低（不合理的查询或缺索引）。</div>
          </div>
          <div class="card-source">来源: 分析性能瓶颈 -> 1. 确定瓶颈的来源</div>
        </div>
      </div>
    </div>

    <div class="card-container" onclick="this.classList.toggle('flipped');">
      <div class="card">
        <div class="card-face card-front">
          <div class="card-category">模式</div>
          <div class="card-question">什么是数据库的垂直分库和水平分库？它们分别适用于什么场景？</div>
          <div class="card-footer">点击卡片查看答案</div>
        </div>
        <div class="card-face card-back">
          <div class="card-category">模式</div>
          <div class="card-answer-wrapper">
            <div class="card-answer">垂直分库是根据业务模块或表的功能将数据拆分到不同数据库，适用于业务逻辑松耦合的场景。水平分库是根据某个维度（如用户ID或时间）将数据分散到多个数据库实例，适用于数据量大且数据访问模式较为均匀的场景。</div>
          </div>
          <div class="card-source">来源: 数据库架构优化 -> 1. 数据库分库分表 -> 1.1 分库</div>
        </div>
      </div>
    </div>

    <div class="card-container" onclick="this.classList.toggle('flipped');">
      <div class="card">
        <div class="card-face card-front">
          <div class="card-category">机制</div>
          <div class="card-question">在使用数据库缓存时，什么是缓存穿透和缓存雪崩？</div>
          <div class="card-footer">点击卡片查看答案</div>
        </div>
        <div class="card-face card-back">
          <div class="card-category">机制</div>
          <div class="card-answer-wrapper">
            <div class="card-answer">缓存穿透指缓存和数据库中都不存在请求的数据，导致请求直接访问数据库，增加数据库压力。缓存雪崩指大量缓存同时过期，导致大量请求直接访问数据库，造成数据库压力暴增。</div>
          </div>
          <div class="card-source">来源: 数据库架构优化 -> 3. 数据库缓存优化 -> 3.2 缓存穿透与缓存雪崩</div>
        </div>
      </div>
    </div>

    <div class="card-container" onclick="this.classList.toggle('flipped');">
      <div class="card">
        <div class="card-face card-front">
          <div class="card-category">策略</div>
          <div class="card-question">为什么在选择索引字段时，应优先选择“选择性高”的字段？</div>
          <div class="card-footer">点击卡片查看答案</div>
        </div>
        <div class="card-face card-back">
          <div class="card-category">策略</div>
          <div class="card-answer-wrapper">
            <div class="card-answer">字段的选择性越高（即字段中唯一值的比例越高），索引的效果就越好。例如，ID、手机号这类字段选择性高，适合建索引；而性别、状态等字段选择性低，索引效果可能不明显，因为查询时仍会扫描大量重复的数据。</div>
          </div>
          <div class="card-source">来源: 索引优化 -> 2. 索引优化策略 -> 2.1 合理选择索引字段</div>
        </div>
      </div>
    </div>

    <div class="card-container" onclick="this.classList.toggle('flipped');">
      <div class="card">
        <div class="card-face card-front">
          <div class="card-category">技术</div>
          <div class="card-question">什么是覆盖索引？它为什么能极大提高查询性能？</div>
          <div class="card-footer">点击卡片查看答案</div>
        </div>
        <div class="card-face card-back">
          <div class="card-category">技术</div>
          <div class="card-answer-wrapper">
            <div class="card-answer">覆盖索引是指索引中包含了查询所需的所有列。它能极大提高性能，因为查询可以直接通过索引返回结果，而无需访问数据表，从而减少了对表的访问。</div>
          </div>
          <div class="card-source">来源: 索引优化 -> 2. 索引优化策略 -> 2.2 选择合适的索引类型</div>
        </div>
      </div>
    </div>

    <div class="card-container" onclick="this.classList.toggle('flipped');">
      <div class="card">
        <div class="card-face card-front">
          <div class="card-category">策略</div>
          <div class="card-question">为什么在优化查询语句时，通常建议避免使用 `SELECT *` 查询？</div>
          <div class="card-footer">点击卡片查看答案</div>
        </div>
        <div class="card-face card-back">
          <div class="card-category">策略</div>
          <div class="card-answer-wrapper">
            <div class="card-answer">因为 `SELECT *` 会返回表中的所有列，而实际业务往往只关心部分字段。通过只查询需要的字段，可以减少返回的数据量，从而减少查询时间和I/O消耗。</div>
          </div>
          <div class="card-source">来源: 优化查询语句 -> 3. 减少返回的数据量</div>
        </div>
      </div>
    </div>

    <div class="card-container" onclick="this.classList.toggle('flipped');">
      <div class="card">
        <div class="card-face card-front">
          <div class="card-category">机制</div>
          <div class="card-question">请简述写通过缓存（Write-through Cache）和写回缓存（Write-back Cache）的机制及其优缺点。</div>
          <div class="card-footer">点击卡片查看答案</div>
        </div>
        <div class="card-face card-back">
          <div class="card-category">机制</div>
          <div class="card-answer-wrapper">
            <div class="card-answer">写通过缓存：数据在写入缓存的同时也会写入底层存储。优点是保证数据一致性，缺点是写操作性能较差。写回缓存：数据首先写入缓存，只有当缓存中的数据被替换或清除时，才会同步更新到底层存储。优点是写操作性能高，缺点是可能存在数据不一致和数据丢失的风险。</div>
          </div>
          <div class="card-source">来源: 数据缓存 -> 3. 缓存的类型</div>
        </div>
      </div>
    </div>

    <div class="card-container" onclick="this.classList.toggle('flipped');">
      <div class="card">
        <div class="card-face card-front">
          <div class="card-category">机制</div>
          <div class="card-question">数据库连接池的工作原理是什么？它为什么能提升系统性能？</div>
          <div class="card-footer">点击卡片查看答案</div>
        </div>
        <div class="card-face card-back">
          <div class="card-category">机制</div>
          <div class="card-answer-wrapper">
            <div class="card-answer">数据库连接池维护了一组连接对象。当应用程序需要访问数据库时，从连接池中获取空闲连接；使用完毕后，连接并不会关闭，而是归还到池中等待下一次使用。这样可以复用已有连接，显著减少了频繁创建和销毁连接的开销，从而提升系统性能。</div>
          </div>
          <div class="card-source">来源: 数据库连接优化 -> 1. 数据库连接池</div>
        </div>
      </div>
    </div>

    <div class="card-container" onclick="this.classList.toggle('flipped');">
      <div class="card">
        <div class="card-face card-front">
          <div class="card-category">理论</div>
          <div class="card-question">什么是乐观锁和悲观锁？它们分别适用于哪些场景？</div>
          <div class="card-footer">点击卡片查看答案</div>
        </div>
        <div class="card-face card-back">
          <div class="card-category">理论</div>
          <div class="card-answer-wrapper">
            <div class="card-answer">悲观锁通过显式地锁定数据来避免数据冲突，适用于高并发冲突的场景，但性能开销较大。乐观锁在更新数据时不加锁，而是在提交时通过版本号等机制判断数据是否被修改，适合冲突较少的场景。</div>
          </div>
          <div class="card-source">来源: 事务与锁优化 -> 2. 锁的优化 -> 2.1 锁粒度优化</div>
        </div>
      </div>
    </div>

      </div>
    </body>
    </html>
